package com.baizhi.product.aspect;

import com.baizhi.product.entity.Log;
import com.fasterxml.jackson.databind.ObjectMapper;
import lombok.SneakyThrows;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.Signature;
import org.aspectj.lang.annotation.After;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.reflect.MethodSignature;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.web.context.request.RequestAttributes;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

import javax.servlet.http.HttpServletRequest;
import java.lang.reflect.Method;
import java.time.LocalDateTime;
import java.util.Arrays;
import java.util.Date;

@Aspect //当前类是一个额外功能类。
@Component //让springboot管理起来这个类
public class LogAspect {
    @Autowired
    private RabbitTemplate rabbitTemplate;
    //后置增强，业务类做完业务操作后，增加记录日志的功能
    @SneakyThrows
    @After("@annotation(com.baizhi.product.aspect.LogAnnotation)")
    public void logAfter(JoinPoint joinPoint){
        //toDo 获取用户名
        String username = "zhangsan";
        //获取系统时间
        LocalDateTime now=LocalDateTime.now();
        //获取用户登录的ip
        RequestAttributes requestAttributes = RequestContextHolder.getRequestAttributes();
        ServletRequestAttributes httpRequestAttributes = (ServletRequestAttributes)requestAttributes;
        HttpServletRequest request = httpRequestAttributes.getRequest();
        String ip = request.getRemoteHost();
        //获取操作类型和操作内容

        Signature signature = joinPoint.getSignature();
        String methodName = signature.getName();
        System.out.println("methodName = " + methodName);

        MethodSignature methodSignature = (MethodSignature)signature;
        Class[] parameterTypes = methodSignature.getParameterTypes();
        System.out.println("parameterTypes = " + Arrays.toString(parameterTypes));

        Method method = joinPoint.getTarget().getClass().getDeclaredMethod(methodName,parameterTypes);
        LogAnnotation annotation = method.getDeclaredAnnotation(LogAnnotation.class);
        String type = annotation.type();
        String content = annotation.content();
        //将以上数据封装为Log实体对象，并调用LogService的addLog方法
        Log log = new Log(null,username,now,ip,type,content);
        ObjectMapper mapper = new ObjectMapper();
        String msg = mapper.writeValueAsString(log);
        rabbitTemplate.convertAndSend("X", "XA", msg);
    }
}
